/*************************************************
 * 
 * Copyright by Bruno Eberhard
 * 
 * Created on 29.07.2005
 *
 *************************************************/
package fightplan.business;

import java.io.Serializable;
import java.util.Date;
import java.util.List;

import fightplan.Mode;
import fightplan.bindx.GLinkedListModel;
import fightplan.bindx.GObservableList;
import fightplan.persistence.ExcelCategoryImport;

public class Tournament implements Serializable {
	private static final long serialVersionUID = 1L;

	@SuppressWarnings("deprecation")
	private static final int year = new Date().getYear() + 1900;

	private String name = "";
	private String place = "";
	private String date = "";
	private boolean children = false;
	private int priceFighter = 15;
	private int priceTeam = 50;
	private String personTournament = "";
	private String personDrawing = "";
	private GObservableList<Category> categories = new GLinkedListModel<Category>();
	private GObservableList<Fighter> fighters = new GLinkedListModel<Fighter>();
	private GObservableList<Dojo> dojos = new GLinkedListModel<Dojo>();
	private Mode mode = Mode.GENERIC;

	public Tournament() {
		setName("Neues Turnier");
	}

	public Tournament(Mode mode) {
		this.mode = mode;
		if (mode == Mode.SKRKYU) {
			ExcelCategoryImport.imprtCategories(this,
					getClass().getResourceAsStream("/Kategorien_SKR_Kyu_Turnier.xls"), true);
			setPriceFighter(10);
			setPriceTeam(30);
		} else if (mode == Mode.SKRKYU_KINDER) {
			ExcelCategoryImport.imprtCategories(this,
					getClass().getResourceAsStream("/Kategorien_SKR_Kyu_Kinder_Turnier.xls"), true);
			setPriceFighter(10);
			setPriceTeam(30);
		} else if (mode == Mode.IPPONSHOBU) {
			ExcelCategoryImport.imprtCategories(this,
					getClass().getResourceAsStream("/Kategorien_SKR_Ippon_Shobu_Cup.xls"), true);
			setPriceFighter(10);
			setPriceTeam(30);
		} else if (mode == Mode.FUJI2008) {
			ExcelCategoryImport.imprtCategories(this, getClass()
					.getResourceAsStream("/Kategorien_FujimuraCup_2009.xls"), true);
		}
		if (mode != Mode.GENERIC) {
			for (int i = 0; i < getCategories().getSize(); i++) {
				getCategories().get(i).setCategoryId(i);
			}
		}
	}

	// get / set

	public String getDate() {
		return date;
	}

	public void setDate(String date) {
		this.date = date;
	}

	/**
	 * @return Year of tournament. Gebraucht für Umrechnung zwischen Jahrgängen
	 *         und Alter
	 */
	public int getYear() {
		return year;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public String getPlace() {
		return place;
	}

	public void setPlace(String place) {
		this.place = place;
	}

	public boolean isChildren() {
		return children;
	}

	public void setChildren(boolean children) {
		this.children = children;
	}

	public int getPriceFighter() {
		return priceFighter;
	}

	public void setPriceFighter(int priceFighter) {
		this.priceFighter = priceFighter;
	}

	public int getPriceTeam() {
		return priceTeam;
	}

	public void setPriceTeam(int priceTeam) {
		this.priceTeam = priceTeam;
	}

	public String getPersonDrawing() {
		return personDrawing;
	}

	public void setPersonDrawing(String personDrawing) {
		this.personDrawing = personDrawing;
	}

	public String getPersonTournament() {
		return personTournament;
	}

	public void setPersonTournament(String personTournament) {
		this.personTournament = personTournament;
	}

	public GObservableList<Category> getCategories() {
		return categories;
	}

	public GObservableList<Fighter> getFighters() {
		return fighters;
	}

	public GObservableList<Dojo> getDojos() {
		return dojos;
	}

	public Dojo getOrCreateDojo(String name) {
		for (int i = 0; i < getDojos().size(); i++) {
			if (getDojos().get(i).getName().equalsIgnoreCase(name)) {
				return getDojos().get(i);
			}
		}
		Dojo dojo = new Dojo();
		dojo.setName(name);
		getDojos().add(dojo);
		return dojo;
	}

	/**
	 * @param fighter
	 * @param kata
	 * @param elite
	 *            true -> nur AgeOpen Kategorien. false -> <i>alle</i>
	 *            Kategorien
	 * @return Nur die Kategorien, in denen der Kämpfer noch nicht angemeldet
	 *         ist.
	 */
	public Category findCategory(Fighter fighter, boolean kata, boolean elite) {
		List<Category> categories = fighter.searchCategories(this);
		for (int i = 0; i < getCategories().size(); i++) {
			Category category = getCategories().get(i);
			if (kata) {
				if (!CategoryType.KATA.equals(category.getCategoryType()))
					continue;
			} else {
				if (!CategoryType.KUMITE.equals(category.getCategoryType()))
					continue;
				if (elite && !category.isAgeOpen())
					continue;
			}
			if (categories.contains(category))
				continue;
			if (!category.compatible(fighter))
				continue;
			return category;
		}
		return null;
	}

	public Category findKumiteCategory(Fighter fighter, int minCategory, int maxCategory) {
		List<Category> categories = fighter.searchCategories(this);
		for (int i = 0; i < getCategories().size(); i++) {
			Category category = getCategories().get(i);
			if (!CategoryType.KUMITE.equals(category.getCategoryType()))
				continue;
			if (category.getCategoryId() < minCategory || category.getCategoryId() > maxCategory)
				continue;
			if (categories.contains(category))
				continue;
			if (!category.compatible(fighter))
				continue;
			return category;
		}
		return null;
	}

	/**
	 * 
	 * @param fighter
	 *            Kämpfer, zu dem die TeamKategorie passen muss
	 * @param kata
	 *            true -> kata, false -> kumite
	 * @return Die erste passende Team - Kategorien. Es wird nicht geprüft, ob
	 *         der Kämpfer schon in einem Team ist, das schon in den Kategorien
	 *         ist.
	 */
	public Category findTeamCategory(Team team) {
		for (int i = 0; i < getCategories().size(); i++) {
			Category category = getCategories().get(i);
			if (!category.compatible(team))
				continue;
			return category;
		}
		return null;
	}

	public Mode getMode() {
		return mode != null ? mode : Mode.GENERIC;
	}

	public void setMode(Mode mode) {
		this.mode = mode;
	}

	/*
	 * public int checkIntegrity() { int errors = 0; for (Category category :
	 * getCategories()) { for (Fighter fighter : category.getFighters()) { if
	 * (!category.compatible(fighter)) { errors++; } } } return errors; }
	 * 
	 * public void enforceIntegrity() { for (Category category :
	 * getCategories()) { List<Fighter> wrongFighters = new
	 * ArrayList<Fighter>(); for (Fighter fighter : category.getFighters()) { if
	 * (!category.compatible(fighter)) { wrongFighters.add(fighter); } }
	 * category.getFighters().removeAll(fighters); for (Fighter fighter :
	 * wrongFighters) { fighter.getCategories().remove(category); } } }
	 */

}